// import QtQuick 1.0 // to target S60 5th Edition or Maemo 5
import QtQuick 1.1
import "character/"

Rectangle {
    id: _playField
    width: 480
    height: 480
    focus: true
    color: "#111111"
    clip: true

    property date prevTime: new Date()
    property date nowTime: new Date()
    property real splitTime: 0

    // 状態管理
    property int loopCount: 1   // ループ回数
    property int score: 0       // 点数
    property int qbCount: 0     // QBの倒した数
    property int homuCount: 5   // ほむの数
    property int enemyMode: 0       // 敵の出現状態 0:QB , 1:Walpr

    property variant playerObject: null
    property real ratio: 0.1    //難易度調整（小さいほうが簡単）
    property int tickCount: 0


    // キーの押されている状態
    property bool isPressLeftKey: false
    property bool isPressRightKey: false
    property bool isPressShotKey: false
    property bool isPressPauseKey: false

    //id
    // 0:やられた
    // 1:ユーザー操作で停止
    signal finishPlay(int id, int score, int loopcount, int qbcount)     // プレイ終了
    signal pausePlay()                  // 一時停止
    signal eyeCatch(int id)             // アイキャッチ
    signal sendInfo(variant obj)        // 情報を上位へ上げる

    Timer{
        id: _mainTimer
        interval: 33
        repeat: true

        onTriggered: {
            // 定期処理
            nowTime = new Date();
            splitTime = nowTime - prevTime;
            prevTime = nowTime;

            // 撃つ
            shotEnemyBullet();
            shotPlayerBullet();

            // 移動
            move();

            // あたり判定
            hitEnemy();
            hitPlayer();

            // 削除
            remove();

            // 一時停止判定
            checkPause();

            // 終了確認
            checkFinish();

            //カウンタ処理
            incrementTickCount();
        }
    }


    // 敵オブジェクトの管理
    Repeater{
        id: _repeaterEnemy
        model: ListModel{
        }
        CharacterLoader{
        }
    }
    // 敵の弾
    Repeater{
        id: _repeaterEnemyBullet
        model: ListModel{
        }
        CharacterLoader{
        }
    }
    // プレーヤーオブジェクトの管理
    Repeater{
        id: _repeaterPlayer
        model: ListModel{
        }
        CharacterLoader{
        }
    }
    // プレーヤーの弾
    Repeater{
        id: _repeaterPlayerBullet
        model: ListModel{
        }
        CharacterLoader{
        }
    }

    // 情報
    Row{
        x: 10
        spacing: 10

        //スコア
        Text{
            id: _score
            color: "#dddddd"
            text: "SCORE : 0"
            font.pixelSize: 16
        }
        //ループ
        Text{
            id: _loopCount
            color: "#dddddd"
            text: "LOOP : 0"
            font.pixelSize: 16
        }
        //QB
        Text{
            id: _qbCount
            color: "#dddddd"
            text: "QB : 0"
            font.pixelSize: 16
        }
        //ほむ
        Text{
            id: _momuCount
            color: "#dddddd"
            text: "HOM : " + homuCount
            font.pixelSize: 16
        }
    }

    // 開始
    function start(){
        _mainTimer.stop();

        // クリア
        isPressLeftKey = false;
        isPressRightKey = false;
        isPressShotKey = false;
        isPressPauseKey = false;
        _repeaterEnemy.model.clear();
        _repeaterEnemyBullet.model.clear();
        _repeaterPlayer.model.clear();
        _repeaterPlayerBullet.model.clear();

        qbCount = 0;
        homuCount = 5;
        score = 0;
        loopCount = 1;
        tickCount = 0;
        ratio = 0.1;
        enemyMode = 0;

        // プレーヤー
        initPlayer();
        // 敵
        initEnemy();

        // タイマー開始
        _mainTimer.start();
    }
    // 再開
    function restart(){
        // クリア
        isPressLeftKey = false;
        isPressRightKey = false;
        isPressShotKey = false;
        isPressPauseKey = false;

        // タイマー再開
        _mainTimer.restart();

        // アニメーション再開
        resumeAnimation();
    }


    function pressed(key){
        switch(key){
        case Qt.Key_Left:
            isPressLeftKey = true;
            break;

        case Qt.Key_Right:
            isPressRightKey = true;
            break;

        case Qt.Key_Space:
            isPressShotKey = true;
            break;

        case Qt.Key_Enter:
        case Qt.Key_Return:
            isPressPauseKey = true;
            break;

        default:
            break;
        }
//        console.debug("press");
    }
    function released(key){
        switch(key){
        case Qt.Key_Left:
            isPressLeftKey = false;
            break;

        case Qt.Key_Right:
            isPressRightKey = false;
            break;

        case Qt.Key_Space:
            isPressShotKey = false;
            break;

        case Qt.Key_Enter:
        case Qt.Key_Return:
            isPressPauseKey = false;
            break;

        default:
            break;
        }
//        console.debug("release");
    }
    Keys.onPressed: {
        pressed(event.key);
    }
    Keys.onReleased: {
        released(event.key);
    }


    // 画面外or削除フラグを消す
    function remove(){
        var i=0;
        var repeater = [_repeaterEnemy, _repeaterPlayer
                        , _repeaterEnemyBullet, _repeaterPlayerBullet];
        for(var r=0; r<repeater.length; r++){
            // 消すので後ろから
            for(i=repeater[r].count-1; i>=0; i--){
                if(repeater[r].itemAt(i).item.isDestory
                        || repeater[r].itemAt(i).item.isOutOfField()){
                    repeater[r].model.remove(i);
                }
            }
        }
    }


    // キャラクタ毎のカウンタ処理
    function incrementTickCount(){
        var i=0;
        var repeater = [_repeaterEnemy, _repeaterPlayer
                        , _repeaterEnemyBullet, _repeaterPlayerBullet];
        if(repeater.length === 0){
            console.debug("tick counter:r=0");
        }
        for(var r=0; r<repeater.length; r++){
            for(i=0; i<repeater[r].count; i++){
                repeater[r].itemAt(i).item.incrementTickCount();
            }
        }
    }

    // 一時停止判定
    function checkPause(){
        if(isPressPauseKey){
            _mainTimer.stop();
            pauseAnimation();
            pausePlay();
        }
    }

    // ゲームの終了判定
    function checkFinish(){
        if(playerObject === null || checkDeadLine()){
            _mainTimer.stop();
            pauseAnimation();
            finishPlay(0, score, loopCount, qbCount);
        }else{
            if(_repeaterEnemy.count === 0){
                if(enemyMode === 0){
                    //QB -> Walpr
                    initWalpurgisnacht();
                    enemyMode = 1;
                }else{
                    //Walpr -> QB

                    //１周した
                    if(ratio < 1.0){
                        ratio += 0.1;
                    }else{
                        ratio = 1.0;
                    }
                    loopCount += 1;
                    enemyMode = 0;
                    initEnemy();

                    // ほむらの絵を変える
                    if(loopCount >= 10){
                        playerObject.burst = 2;
                    }else if(loopCount >= 3){
                        playerObject.burst = 1;
                    }else{
                        playerObject.burst = 0;
                    }

                    //アイキャッチ
                    if(loopCount == 2){
                        // みんな騙されてる
                        _mainTimer.stop();
                        pauseAnimation();
                        eyeCatch(0);
                    }else if(loopCount == 3){
                        // もうだれもたよらない
                        _mainTimer.stop();
                        pauseAnimation();
                        eyeCatch(2);
                    }else if(loopCount == 10){
                        // エンディング
                        _mainTimer.stop();
                        pauseAnimation();
                        eyeCatch(10);
                    }else{
                        // もういちど
                        _mainTimer.stop();
                        pauseAnimation();
                        eyeCatch(1);
                    }
                }

            }

            // 情報更新
            tickCount++;
            if(tickCount > 0xffffff){
                tickCount = 0;
            }
            if((tickCount % 15) === 0){
                sendInfo({"count": "e=" + _repeaterEnemy.count + ",eb=" + _repeaterEnemyBullet.count
                                   + ",p=" + _repeaterPlayer.count + ",pb=" + _repeaterPlayerBullet.count
                                   + ",fps=" + (1000 / splitTime)
                         });
            }
            if((tickCount % 10) === 0){
                _score.text = "SCORE : " + score;
                _loopCount.text = "LOOP : " + loopCount;
                _qbCount.text = "QB : " + qbCount;
            }
        }
    }

    // 敵がデッドライン超えたか？
    function checkDeadLine(){
        var ret = false;
        var i=0;
        var obj = null;
        var repeater = [_repeaterEnemy, _repeaterPlayer];
        for(var r=0; r<repeater.length; r++){
            for(i=0; i<repeater[r].count; i++){
                obj = repeater[r].itemAt(i).item;
                if((obj.y + obj.height) > _playField.height){
                    // 敵がデッドライン超えた
                    ret = true;
                }
            }
        }
        return ret;
    }

    // 一時停止解除からアニメーションを再開
    function resumeAnimation(){
        var i=0;
        var repeater = [_repeaterEnemy, _repeaterPlayer
                        , _repeaterEnemyBullet, _repeaterPlayerBullet];
        for(var r=0; r<repeater.length; r++){
            for(i=0; i<repeater[r].count; i++){
                repeater[r].itemAt(i).item.resumeAnimation();
            }
        }
    }

    // 一時停止用にアニメーションを止める
    function pauseAnimation(){
        var i=0;
        var repeater = [_repeaterEnemy, _repeaterPlayer
                        , _repeaterEnemyBullet, _repeaterPlayerBullet];
        for(var r=0; r<repeater.length; r++){
            for(i=0; i<repeater[r].count; i++){
                repeater[r].itemAt(i).item.pauseAnimation();
            }
        }
    }


    //キャラIDの発行
    property int lastCharId: -1
    function getCharId(){
        return lastCharId + 1;
    }

    // 敵　初期的配置
    function initEnemy(){
        var w = 30;
        var h = 30;
        var s = 10;
        var offset_x = 10;
        var offset_y = 30;

        var type = 0;

        if(loopCount >= 10){
            type = 2;
        }else if(loopCount >= 3){
            type = 1;
        }else{
            type = 0;
        }

        // クリア
        _repeaterEnemy.model.clear();
        _repeaterEnemyBullet.model.clear();
        _repeaterPlayerBullet.model.clear();
        // 配置
//        for(var i=0; i<1; i++){
//            for(var k=0; k<1; k++){
        for(var i=0; i<5; i++){
            for(var k=0; k<10; k++){
                _repeaterEnemy.model.append({"_qml": "Enemy.qml"
                                                , "_charId": getCharId()
                                                , "_x": (w + s) * k + offset_x
                                                , "_y": (h + s) * i + offset_y
                                                , "_fieldWidth": _playField.width
                                                , "_fieldHeight": _playField.height
                                                , "_scorepoint": 100
                                                , "_hitpoint": 2
                                                , "_ratio": ratio
                                                , "_init":{"_type": type}
                                            });
            }
        }
    }
    function initWalpurgisnacht(){
        var type = 0;

        if(loopCount >= 10){
            type = 1;
        }else{
            type = 0;
        }

        // クリア
        _repeaterEnemy.model.clear();
        // 配置
        _repeaterEnemy.model.append({"_qml": "Walpurgisnacht.qml"
                                        , "_charId": getCharId()
                                        , "_x": width / 2 - 150
                                        , "_y": 50
                                        , "_fieldWidth": _playField.width
                                        , "_fieldHeight": _playField.height
                                        , "_scorepoint": 1000
                                        , "_hitpoint": 80
                                        , "_ratio": ratio
                                        , "_init":{"_type": type}
                                    });
    }

    // プレーヤー初期配置
    function initPlayer(){
        var pid = getCharId();
        _repeaterPlayer.model.clear();
        _repeaterPlayer.model.append({"_qml": "Player.qml"
                                        , "_charId": pid
                                        , "_x": _playField.width / 2 - 15
                                        , "_y": _playField.height - 30 - 10
                                         , "_fieldWidth": _playField.width
                                         , "_fieldHeight": _playField.height
                                         , "_scorepoint": 0
                                         , "_hitpoint": 5
                                         , "_ratio": ratio
                                    });
        playerObject = _repeaterPlayer.itemAt(0).item;
        playerObject.burst = 0;
    }

    // 弾を撃つ（敵が）
    function shotEnemyBullet(){
        var obj = null;
        var data = null;
        for(var i=0; i<_repeaterEnemy.count; i++){
            obj = _repeaterEnemy.itemAt(i).item;
            while((data = obj.getBullet()) !== null){
                data._charId = getCharId();
                _repeaterEnemyBullet.model.append(data);
            }
        }
    }

    // 弾を撃つ
    function shotPlayerBullet(){
        if(!isPressShotKey){
        }else if(playerObject === null){
        }else if(_repeaterPlayerBullet.count < 5){
            var shot = false;
            if(_repeaterPlayerBullet.count === 0){
                shot = true;
            }else if(_repeaterPlayerBullet.itemAt(_repeaterPlayerBullet.count - 1).item.tickCount > 10){
                shot = true;
            }else{
            }
            if(shot){
                var data = playerObject.getBullet();
                data.pid = getCharId();
                _repeaterPlayerBullet.model.append(data);
            }
        }
    }




    // 移動
    function move(){
        var i=0;
        var repeater = [_repeaterEnemy, _repeaterPlayer
//                        , _repeaterEnemyBullet, _repeaterPlayerBullet
                ];
        for(var r=0; r<repeater.length; r++){
            for(i=0; i<repeater[r].count; i++){
                repeater[r].itemAt(i).item.move(isPressLeftKey, isPressRightKey);
            }
        }
    }

    // 敵の当たり判定
    function hitEnemy(){
        var i=0;
        var b=0;
        var enemy = null;
        var bullet = null;
        for(i=0; i<_repeaterEnemy.count; i++){
            enemy = _repeaterEnemy.itemAt(i).item;

            if(enemy.hitpoint > 0){
                for(b=0; b<_repeaterPlayerBullet.count; b++){
                    bullet = _repeaterPlayerBullet.itemAt(b).item;

                    if(bullet.checkHit(enemy.x, enemy.y, enemy.width, enemy.height)){
                        // hit
                        var se = enemy.hit();
                        var sb = bullet.hit();
                        if(se > 0){
                            // 倒した
    //                        console.debug("se=" + se + ",s=" + se / bullet.tickCount);
                            score += (se / bullet.tickCount) * (1 + ratio);
                            if(enemyMode === 0 && loopCount >= 3 && loopCount < 10){
                                qbCount++;
                            }
                        }
                    }else{
                    }
                }
            }
        }
    }

    // プレーヤーの当たり判定
    function hitPlayer(){
        if(playerObject !== null){
            var i=0;
            var obj = null;
            // 敵本体との当たり判定
            for(i=0; i<_repeaterEnemy.count; i++){
                obj = _repeaterEnemy.itemAt(i).item;
                if(obj.checkHit(playerObject.x, playerObject.y, playerObject.width, playerObject.height)){
                    //hit
                    playerObject.hit();
                }
            }
            // 敵の弾との当たり判定
            for(i=0; i<_repeaterEnemyBullet.count; i++){
                obj = _repeaterEnemyBullet.itemAt(i).item;
                if(obj.checkHit(playerObject.x, playerObject.y, playerObject.width, playerObject.height)){
                    //hit
                    playerObject.hit();
                    obj.hit();
                    homuCount = playerObject.hitpoint;
                }
            }
        }
    }
}
